#!/usr/bin/env python
'''
    creates and updates docindexer document indexes

SYNOPSIS
    Execute script with --help option to view synopsis.

HOME PAGE
    http://www.methods.co.nz/docindexer/

COPYING
    Copyright (C) 2007 Stuart Rackham. Free use of this software is
    granted under the terms of the MIT License.
'''
__author__ = 'Stuart Rackham <srackham@methods.co.nz>'
# The following line is set automatically from main.aap
__version__ = '0.9.4.3'

import sys, os
from docindexer.common import EDocIndexer, Conf, Log, decode_input, safe_print
from docindexer.parsers import Parsers
from docindexer.docindexer import DocIndexer

def printconf():
    ''' Print configuration command.'''
    fmt = '%-10s%-30s%s'
    print fmt % ('File Ext','MIME Type','Parser')
    print fmt % ('--------','---------','------')
    exts = Conf.mime_dict.keys()
    exts.sort()
    for ext in exts:
        mime = Conf.mime_dict[ext]
        for parser in Parsers.builtin_parsers:
            if parser.handles(mime):
                print fmt % (ext, mime, parser.description)

def main():
    def args_error(msg):
        print options.get_usage()
        safe_print('%s: error: %s' % (os.path.basename(sys.argv[0]),msg))
        sys.exit(1)
    # Process command line options.
    import optparse
    usage='usage: %prog [options] [docsdir] [files...]'
    version='%%prog %s' % __version__
    options = optparse.OptionParser(usage=usage,version=version)
    options.add_option('-a', '--analyze',
        action='store_true',
        dest='analyze',
        help='analyze file and write words to stdout')
    options.add_option('-c', '--config',
        action='store_true',
        dest='conf',
        help='print configuration information')
    options.add_option('-e', '--excludes',
        action='store',
        type='string',
        dest='excludes',
        metavar='WILDCARDS',
        help='one or more | separated wildcards')
    options.add_option('-i', '--includes',
        action='store',
        type='string',
        dest='includes',
        metavar='WILDCARDS',
        help='one or more | separated wildcards')
    options.add_option('-F', '--format',
        action='store',
        type='string',
        dest='format',
        metavar='FORMAT',
        help='list format')
    options.add_option('-l', '--list',
        action='store_true',
        dest='list',
        help='print a list of indexed documents')
    options.add_option('-L', '--logfile',
        action='store',
        type='string',
        dest='logfile',
        metavar='FILE',
        help='write log messages to file')
    options.add_option('-n', '--dry-run',
        action='store_true',
        dest='dryrun',
        help='do not update the index')
    options.add_option('-q', '--quiet',
        action='store_true',
        dest='quiet',
        help='suppress stdout while indexing')
    options.add_option('-r', '--rebuild',
        action='store_true',
        dest='rebuild',
        help='rebuild the index')
    options.add_option('-s', '--summary',
        action='store_true',
        dest='summary',
        help='print a summary of index statistics')
    options.add_option('-t', '--text',
        action='store_true',
        dest='text',
        help='parse file and write textual content to stdout')
    (opts, args) = options.parse_args()
    args = [decode_input(s.strip()) for s in args]
    # Do the work.
    if options.values.logfile is not None:
        Log.stream = open(options.values.logfile,'w+')
    else:
        Log.stream = sys.stdout
    if options.values.conf:
        printconf()
        return
    if len(args) < 1:
        args_error('incorrect number of arguments')
    if options.values.analyze:
        if len(args) == 1 and os.path.isfile(args[0]):
            content = DocIndexer.file_to_text(args[0])
        else:
            content = decode_input(' '.join(args),'replace')
        import StringIO
        DocIndexer.analyze(StringIO.StringIO(content), sys.stdout)
        return
    if options.values.text:
        text = DocIndexer.file_to_text(args[0])
        safe_print(text)
        return
    indexer = DocIndexer(docsdir=args[0])
    if options.values.format is not None:
        indexer.format = options.values.format
    if options.values.list or options.values.summary:
        indexer.check_index_exists()
        indexer.printf(options.values.list, options.values.summary)
    else:
        indexer.rebuild = options.values.rebuild
        indexer.dryrun = options.values.dryrun
        if options.values.includes is not None:
            indexer.includes = [s.strip() for s in options.values.includes.split('|')]
        if options.values.excludes is not None:
            indexer.excludes = [s.strip() for s in options.values.excludes.split('|')]
        if options.values.quiet:
            Log.quiet = True
        files_to_index = args[1:]
        indexer.log_header()
        indexer.parsers.open()
        try:
            if files_to_index:
                indexer.update_files(files_to_index)
            else:
                indexer.update_index()
        finally:
            indexer.parsers.close()
            indexer.log_footer()


if __name__ == '__main__':
    __pychecker__ = 'no-badexcept'  # KeyboardInterrupt is OK.
    try:
        main()
    except EDocIndexer,e:
        Log.error('failed: %s' % e)
        sys.exit(1)
    except KeyboardInterrupt:
        Log.error('user keyboard interrupt')
        sys.exit(1)

# vim: set ts=4 sw=4:
